package com.netty.listener;

import java.util.concurrent.TimeUnit;

import java.util.concurrent.locks.LockSupport;

import com.netty.handler.ClientMessageHandler;
import com.netty.handler.DefaultChannelPoolHandler;
import com.netty.util.WrapperRequestMessage;
import com.netty.util.WrapperResponseMessage;

import io.netty.channel.Channel;
import io.netty.channel.ChannelPipeline;
import io.netty.util.concurrent.Future;
import io.netty.util.concurrent.GenericFutureListener;
/**
 * 默认消息收发监听器
 * @author hmm
 *
 */
public class DefaultGenericFutureListener implements GenericFutureListener<Future<Channel>> {

	private WrapperResponseMessage wrapperResponse;
	private WrapperRequestMessage wrapperRequest;
	private Thread thread = Thread.currentThread();
	
	public DefaultGenericFutureListener(WrapperResponseMessage wrapperResponse,
			WrapperRequestMessage wrapperRequest) {
		this.wrapperResponse = wrapperResponse;
		this.wrapperRequest = wrapperRequest;
	}

	@Override
	public void operationComplete(Future<Channel> future) throws Exception {
		if(future.isSuccess()){
			 Channel channel = future.getNow();
			 ChannelPipeline pipeline = channel.pipeline();
			 ClientMessageHandler messageHandler = (ClientMessageHandler) pipeline.get(DefaultChannelPoolHandler.MESSAGE_HANDLER);
			 messageHandler.setWrapper(this.wrapperResponse);
			 messageHandler.setThread(this.thread);
			 channel.writeAndFlush(this.wrapperRequest.getBody());
		}
		
		future.removeListener(this);
	}

	public WrapperResponseMessage get(){
		LockSupport.park(this.thread);
		return this.wrapperResponse;
	}
	
	public WrapperResponseMessage get(long time, TimeUnit unit){
		long deadline = System.nanoTime() + unit.toNanos(time);
		for(;;){
			if(!wrapperResponse.isEmpty()){
				return this.wrapperResponse;
			}
			long nanos = deadline - System.nanoTime();
			if(nanos <= 0L){
				System.out.println("超时！！！");
				return this.wrapperResponse;
			}
			LockSupport.parkNanos(this.thread, nanos);
		}
	}
	
}
